<?php declare(strict_types=1);


namespace App\Controller;

use App\Common\Response;
use App\Exception\DaoException;
use App\Exception\LogicException;
use App\Model\Event;
use App\Model\EventInfo;
use App\Model\PackDownLog;
use App\Service\PackDownLogService;
use Exception;
use Hyperf\Di\Annotation\Inject;
use Psr\Http\Message\ResponseInterface;


class AdminController extends AbstractController
{
    /**
     * @Inject()
     * @var PackDownLogService
     */
    protected PackDownLogService $service;



    /**
     * 下载某期事件的所有包，
     * @throws Exception
     */
    public function downloadEventPack(): ResponseInterface
    {
        $params = $this->getParams();
        $user = $this->getUser();
        var_dump($params);
        // 简单做一下用户判断
        if((int)$user['is_admin'] !== 1){
            return $this->response->json(Response::fail('非法操作'));
        }
        $event = Event::query()->where('id', (int)($params['event_id'] ?? 0))->first();

        // 查询事件详情表，获取事件的所有文件记录
        $eventData = EventInfo::query()->where('event_id',(int)($event->id))
            ->orderBy('created_at','desc')
            ->with('filesPath')
            ->select([
                'submitter_id',
                'id',
                'event_name',
                'event_id',
                'created_at'
            ])
            ->get()->toArray();
        if(!$eventData) {
            return $this->response->json(Response::fail('没有文件'));
        }
        // 遍历获取文件名和位置，复制到新的位置并使用新的文件名
        $baseDirName = md5(microtime());
        $relativeDir = '/runtime/event_pack/' . date('Y-m-d');
        $basePath = BASE_PATH . $relativeDir;
        $basePathTmp = $basePath.'/'. $baseDirName;
        if (!is_dir($basePathTmp) && !mkdir($basePathTmp, 0777, true) && !is_dir($basePathTmp)) {
            return $this->response->json(
                Response::fail(
                    sprintf('Directory "%s" was not created', $basePathTmp)
                )
            );
        }
        // 每个同学
        foreach ($eventData as $index => $student) {
            // 同学的文件
            foreach ($student['files_path'] as $file) {
                $fileName = $file['file_name'];
                $filePath = $file['path'];
                if(!is_file(BASE_PATH.'/'.$filePath)) {
                    continue;
                }
                // 逐个文件复制
                copy(BASE_PATH.'/'.$filePath, $basePathTmp.'/'.$fileName);
            }
        }

        // 压缩文件，删除旧文件
        $zipFilename = $event->name.'.zip';
        $path = $basePath.'/'.$zipFilename;

        $command = sprintf('zip -j %s %s/*', $path, $basePathTmp);
        exec($command);
        exec('rm -r ' . $basePathTmp);

        // 写入日志记录
        $model = new PackDownLog();
        $model->hash = $baseDirName;
        $model->event_id = $event->id;
        $model->event_name = $event->name;
        $model->file_name = $event->name.'.zip';
        $model->created_by = $user['nick_name'];
        $model->created_id = $user['id'];
        $model->path = $relativeDir.'/'.$zipFilename;
        $model->save();

        // 返回结果 给浏览器下载
        return $this->response->json(Response::success(['hash'=>$model->hash],'打包成功，正在下载...'));
    }

    /**
     * 文件下载，路由在routes文件
     * @param string hash
     * @return ResponseInterface
     */
    public function d(): ResponseInterface
    {
        try{
            $params = $this->getParams();
            $file = $this->service->download($params['hash'] ?? '');
            if(!is_file(BASE_PATH .'/' .$file->path)) {
                return $this->response->json(['nofile']);
            }
            return $this->response->download(BASE_PATH .'/' .$file->path, $file->file_name);
        }catch (LogicException | DaoException $e) {
            return $this->response->json(Response::fail($e->getMessage()));
        }
    }


}